package com.bangdream.michelia.tool.retrofithttp;

import android.annotation.SuppressLint;
import android.util.Log;

import com.alibaba.fastjson.JSON;
import com.bangdream.michelia.application.AppCurrentUser;
import com.bangdream.michelia.application.MainApplication;
import com.bangdream.michelia.entity.BaseEntity;
import com.bangdream.michelia.entity.UserInfoBean;
import com.bangdream.michelia.tool.rejava.BaseObserverEntityNormalHttp;
import com.bangdream.michelia.utils.SPUtils;

import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.concurrent.atomic.AtomicBoolean;

import io.reactivex.Observable;
import io.reactivex.ObservableEmitter;
import io.reactivex.ObservableOnSubscribe;
import io.reactivex.ObservableSource;
import io.reactivex.Observer;
import io.reactivex.android.schedulers.AndroidSchedulers;
import io.reactivex.annotations.NonNull;
import io.reactivex.disposables.Disposable;
import io.reactivex.functions.Consumer;
import io.reactivex.functions.Function;
import io.reactivex.observers.DisposableObserver;
import io.reactivex.schedulers.Schedulers;
import io.reactivex.subjects.PublishSubject;
import okhttp3.MediaType;
import okhttp3.RequestBody;

public class TokenLoader {
    private static final String TAG = "okhttp";

    private AtomicBoolean mRefreshing = new AtomicBoolean(false);
    private PublishSubject<BaseEntity<UserInfoBean>> mPublishSubject;
    private Observable<BaseEntity<UserInfoBean>> mTokenObservable;

    @SuppressLint("CheckResult")
    private TokenLoader() {
        mPublishSubject = PublishSubject.create();


        Map<String, String> map = new HashMap<>();
        map.put("accountName", (String) SPUtils.get(MainApplication.getContext(), "userName", ""));
        map.put("loginType", "1");
        map.put("password", (String) SPUtils.get(MainApplication.getContext(), "pwd", "123456"));
        map.put("type", "2");
        String jsonString = JSON.toJSONString(map);
        RequestBody requestBody = RequestBody.create(MediaType.parse("application/json; charset=utf-8"),
                jsonString);
        Log.d(TAG, "请求Token");
        mTokenObservable=RetroFactory.getInstance().actionLogin(requestBody).doOnNext(new Consumer<BaseEntity<UserInfoBean>>() {
            @Override
            public void accept(BaseEntity<UserInfoBean> beanBaseEntity) throws Exception {
                Log.d(TAG, "请求Token--------doOnNext");

                if (beanBaseEntity.getData() != null && beanBaseEntity.getData().getToken() != null){
                    Log.d(TAG, "存储Token=" + beanBaseEntity.getData().getToken());
                    AppCurrentUser.getInstance().setToken(beanBaseEntity.getData().getToken());

                }
                mRefreshing.set(false);
            }
        }).doOnError(new Consumer<Throwable>() {
            @Override
            public void accept(Throwable throwable) throws Exception {
                Log.d(TAG, "请求Token--------doOnError");

                mRefreshing.set(false);
            }
        }).subscribeOn(Schedulers.io());

    }

    public static TokenLoader getInstance() {
        return Holder.INSTANCE;
    }

    private static class Holder {
        private static final TokenLoader INSTANCE = new TokenLoader();
    }

    public String getCacheToken() {
        return AppCurrentUser.getInstance().getToken();
    }

    public Observable<BaseEntity<UserInfoBean>> getNetTokenLocked() {
        if (mRefreshing.compareAndSet(false, true)) {
            Log.d(TAG, "没有请求，发起一次新的Token请求");
            startTokenRequest();
        } else {
            Log.d(TAG, "已经有请求，直接返回等待");
        }
        return mPublishSubject;
    }

    private void startTokenRequest() {

        mTokenObservable.subscribe(mPublishSubject);
    }


//    private void startTokenRequest() {
//        Map<String, String> map = new HashMap<>();
//        map.put("accountName", (String) SPUtils.get(MainApplication.getContext(), "userName", ""));
//        map.put("loginType", "1");
//        map.put("password", (String) SPUtils.get(MainApplication.getContext(), "pwd", "123456"));
//        map.put("type", "2");
//        String jsonString = JSON.toJSONString(map);
//        RequestBody requestBody = RequestBody.create(MediaType.parse("application/json; charset=utf-8"),
//                jsonString);
//        Log.d(TAG, "请求Token");
//        RetroFactory.getInstance().actionLogin(requestBody)
//                .flatMap(new Function<BaseEntity<UserInfoBean>, ObservableSource<BaseEntity<UserInfoBean>>>() {
//                    @Override
//                    public ObservableSource<BaseEntity<UserInfoBean>> apply(BaseEntity<UserInfoBean> beanBaseEntity) throws Exception {
//                        //这里检测后台返回数据是否正确
//                        return Observable.just(beanBaseEntity);
//                    }
//                })
//                //.retry(2)//重试2次 这里后期可以优化 检测异常是否触发回调
//                .doOnNext(new Consumer<BaseEntity<UserInfoBean>>() {
//                    @Override
//                    public void accept(BaseEntity<UserInfoBean> beanBaseEntity) throws Exception {
//                        Log.d(TAG, "存储Token=doOnNext");
//
//                        if(beanBaseEntity.getData()!=null && beanBaseEntity.getData().getToken()!=null){
//                            Log.d(TAG, "存储Token=" + beanBaseEntity.getData().getToken());
//
//                            AppCurrentUser.getInstance().setToken(beanBaseEntity.getData().getToken());
//                            notifySuccess(beanBaseEntity);
//                        }else{
////                            throw new Exception("获取token失败");
//                        }
//                    }
//                }).doOnError(new Consumer<Throwable>() {
//                    @Override
//                    public void accept(Throwable throwable) throws Exception {
//                        Log.d(TAG, "throwable=" + throwable.getMessage());
//                        notifyError(throwable);
//                    }
//                })
//                .subscribeOn(Schedulers.io())
//                .onErrorResumeNext(Observable.<BaseEntity<UserInfoBean>>never())
//                .subscribe();
//
//    }
}
